package com.pro.common.modules.service.dependencies.commondata.controller;

import com.pro.common.api.enums.EnumSysRole;
import com.pro.common.api.exception.BusinessException;
import com.pro.common.api.model.ILoginInfo;
import com.pro.common.api.model.IUserIdClass;
import com.pro.common.modules.service.dependencies.commondata.service.CommonTableService;
import com.pro.framework.api.util.AssertUtil;
import com.pro.framework.api.util.CollUtils;
import com.pro.framework.api.util.StrUtils;
import com.pro.framework.javatodb.model.*;
import com.pro.framework.javatodb.model.request.JTDTableInfoRequest;
import com.pro.framework.javatodb.service.JTDServiceImpl;
import com.pro.framework.javatodb.util.JTDUtil;
import com.pro.framework.mtq.service.multiwrapper.entity.IMultiClassRelation;
import com.pro.framework.mtq.service.multiwrapper.util.MultiClassRelationFactory;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.AllArgsConstructor;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.lang.reflect.Field;
import java.util.*;
import java.util.function.Predicate;
import java.util.stream.Collectors;

@Tag(name = "统一数据结构信息")
@Slf4j
@RestController
@RequestMapping("/commonTable")
@AllArgsConstructor
public class CommonTableStructInfoController {
    private CommonTableService commonTableService;
    private JTDServiceImpl jtDService;

    @SneakyThrows
    @Operation(summary = "查询表格构造信息")
    @GetMapping("/getTableSimples/{entityClassNames}")
    public Map<String,JTDTableInfo> getTableSimples(@PathVariable("entityClassNames") String entityClassNames) {
        return CollUtils.listToMap(Arrays.stream(entityClassNames.split(","))
                .map(c->{
                    JTDTableInfo table = jtDService.buildTableFullInfoFromClass(
                            MultiClassRelationFactory.INSTANCE.getEntityClass(c));
                    table.setEntityName(c);
                    table.setTableName(null);
                    table.setFields(null);
                    table.setSequences(null);
                    table.setExcludeFieldNames(null);
                    table.setTableName(null);
                    return table;
                }).toList(),JTDTableInfo::getEntityName);
    }


    @SneakyThrows
    @Operation(summary = "查询完整表格构造信息", description = "admin端才可以访问")
    @GetMapping("/getTables")
    public List<JTDTableInfoVo> getTables(@Parameter(hidden = true) ILoginInfo loginInfo) {
        // 测试或本地 或者 管理端登录 才能访问
        if (null != loginInfo && loginInfo.getIsDemo()) {
            Collection<Class<?>> classes = MultiClassRelationFactory.INSTANCE.getClassMap().values();
            Predicate<Field> fieldFilter = JTDUtil::fieldFilter;
            Map<String, List<IMultiClassRelation>> relationListMap = MultiClassRelationFactory.INSTANCE.getRelations()
                    .stream()
                    .collect(Collectors.groupingBy(IMultiClassRelation::getClassName1));
            return classes.stream().map(c -> {
                JTDTableInfoVo tableSimpleInfo = commonTableService.getTableSimpleInfo(
                        StrUtils.firstToLowerCase(c.getSimpleName()), fieldFilter);
                tableSimpleInfo.setExtend(relationListMap.get(StrUtils.firstToLowerCase(c.getSimpleName())));
                return tableSimpleInfo;
            }).sorted(Comparator.comparing(JTDTableInfoVo::getEntityId).reversed()).collect(Collectors.toList());
        }
        return null;
    }

    @SneakyThrows
    @Operation(summary = "查询完整表格构造信息")
    @GetMapping("/info/{entityClassName}")
    public UITableInfo info(@Parameter(hidden = true) ILoginInfo loginInfo, @PathVariable("entityClassName") String entityClassName, JTDTableInfoRequest request) {
        checkPermission(loginInfo, entityClassName);
        return commonTableService.getTableStruct(entityClassName, request);
    }

    @SneakyThrows
    @Operation(summary = "查询概要表格信息")
    @GetMapping(value = "/simpleInfo/{entityClassName}")
    public JTDTableInfoVo getTableSimpleInfo(@Parameter(hidden = true) ILoginInfo loginInfo, @PathVariable("entityClassName") String entityClassName) {
        checkPermission(loginInfo, entityClassName);
        Predicate<Field> fieldFilter = JTDUtil::fieldFilter;
        return commonTableService.getTableSimpleInfo(entityClassName, fieldFilter);
    }

    private void checkPermission(@Parameter(hidden = true) ILoginInfo loginInfo, String entityClassName) {
        switch (loginInfo.getSysRole()) {
            case ADMIN:
            case AGENT:
            case USER:
                if (loginInfo.getId() == null || EnumSysRole.ANONYMOUS.equals(loginInfo.getSysRole())) {
                    throw new BusinessException(403, "暂无权限");
                }
                break;
            default:
                throw new BusinessException(403, "暂无权限");
        }
        switch (loginInfo.getSysRole()) {
            case ADMIN:
                break;
            case AGENT:
            case USER:
                Class<?> beanClass = MultiClassRelationFactory.INSTANCE.getEntityClass(entityClassName);
                AssertUtil.isTrue(IUserIdClass.class.isAssignableFrom(beanClass), "暂无权限");
                break;
            default:
                throw new BusinessException(403, "暂无权限");
        }
    }


}
